#ifndef _MALICE_CODEGEN_H_
#define _MALICE_CODEGEN_H_

#include <vector>
#include <tr1/unordered_map>

#include "MAlice.hpp"
#include "Ast/Ast.h"

namespace MAlice
{

typedef IRBuilder<> Builder;

class Codegen
{
public:
	typedef unordered_map<string, Type*> TypeIds;
	typedef unordered_map<string, Value*> ScopeType;

private:
	TypeIds mTypeIds;
	Module * mModule;
	Builder * mBuilder;
	LLVMContext mContext; ///< LLVM context of the code generator
	vector<ScopeType> mVars;

public:
	/**
	 * @return singleton instance of {#link Codegen}
	 * */
	static Codegen* get();

	Codegen();

	/** getters @{ */
	LLVMContext& getContext();
	Builder* getBuilder();
	Module* getModule();
	/** getters @} */

	/**
	 * @return Value* of a named type in the scope of the program or NULL if not found
	 * */
	Value* getVar(const string& name);
	void pushVar(const string& name, Value* value);
	void pushScope();
	void popScope();

	/**
	 * @return a map of type name into llvm::Type*
	 * */
	TypeIds& getTypeIds();
};

} // namespace MAlice

#endif /* _MALICE_CODEGEN_H_ */
